import os, sys, math
from tkinter import *
from PIL import Image  # <== required for thumbs
from PIL.ImageTk import PhotoImage  # <== required for JPEG display


def makeThumbs(imgdir, size=(100, 100), subdir='thumbs'):
    """
    创建缩略图
    imgdir：图片路径
    size：缩略图大小
    subdir：缩略图目录
    """
    thumbdir = os.path.join(imgdir, subdir)
    if not os.path.exists(thumbdir):
        os.mkdir(thumbdir)

    thumbs = []
    for imgfile in os.listdir(imgdir):
        thumbpath = os.path.join(thumbdir, imgfile)
        # 如果缩略图已经存在
        if os.path.exists(thumbpath):
            thumbobj = Image.open(thumbpath)
            thumbs.append((imgfile, thumbobj))
        else:
            print('制作缩略图：', thumbpath)
            imgpath = os.path.join(imgdir, imgfile)
            try:
                # 制作新的缩略图
                imgobj = Image.open(imgpath)
                imgobj.thumbnail(size, Image.ANTIALIAS)
                imgobj.save(thumbpath)
                thumbs.append((imgfile, imgobj))
            except:
                print("跳过文件路径: ", imgpath)
    return thumbs


class ViewOne(Toplevel):
    """
    查看单张图片
    """
    def __init__(self, imgdir, imgfile):
        Toplevel.__init__(self)
        self.title(imgfile)
        # 图片路径
        imgpath = os.path.join(imgdir, imgfile)
        # 图片对象
        imgobj = PhotoImage(file=imgpath)
        # 图片标签
        Label(self, image=imgobj).pack()
        # 查看图片的宽高
        print(imgpath, imgobj.width(), imgobj.height())
        # 保留引用
        self.savephoto = imgobj


def viewer(imgdir, kind=Toplevel, cols=None):
    """
    网格化布局
    """
    win = kind()
    win.title('查看图片文件夹: ' + imgdir)
    thumbs = makeThumbs(imgdir)
    if not cols:
        cols = int(math.ceil(math.sqrt(len(thumbs))))

    rownum = 0
    savephotos = []
    while thumbs:
        thumbsrow, thumbs = thumbs[:cols], thumbs[cols:]
        colnum = 0
        for (imgfile, imgobj) in thumbsrow:
            photo = PhotoImage(imgobj)
            link = Button(win, image=photo)
            handler = lambda savefile=imgfile: ViewOne(imgdir, savefile)
            link.config(command=handler)
            # 创建网格，行，列
            link.grid(row=rownum, column=colnum)
            savephotos.append(photo)
            # 列增加
            colnum += 1
        # 行增加
        rownum += 1

    Button(win, text='退出', command=win.quit).grid(columnspan=cols, stick=EW)
    return win, savephotos


if __name__ == '__main__':
    imgdir = 'C:\\Users\\18010\\Pictures\\bg'
    main, save = viewer(imgdir, kind=Tk)
    main.mainloop()
